package cn.silver.module.web.controller;

import cn.dev33.satoken.annotation.SaIgnore;
import cn.hutool.core.util.RandomUtil;
import cn.silver.framework.core.constant.Constants;
import cn.silver.framework.core.constant.GlobalConstants;
import cn.silver.framework.mail.properties.MailProperties;
import cn.silver.framework.mail.utils.MailUtils;
import cn.silver.framework.openapi.constant.ResultEnum;
import cn.silver.framework.openapi.model.Result;
import cn.silver.framework.redis.utils.RedisUtils;
import cn.silver.framework.web.enums.CaptchaTypeEnums;
import cn.silver.module.authority.bean.ClientBean;
import cn.silver.module.authority.domain.SysClient;
import cn.silver.module.authority.service.ISysClientService;
import cn.silver.module.web.model.CaptchaModel;
import cn.silver.module.web.service.SysCaptchaService;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import io.swagger.v3.oas.annotations.tags.Tag;
import jakarta.validation.constraints.NotBlank;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;

import java.time.Duration;
import java.util.LinkedHashMap;

/**
 * 验证码操作处理
 *
 * @author Lion Li
 */
@Slf4j
@SaIgnore
@Validated
@RestController
@Tag(name = "验证码管理")
@RequiredArgsConstructor
@RequestMapping("/captcha")
public class CaptchaController {

    private final SysCaptchaService baseService;
    private final ISysClientService clientService;
    private final MailProperties mailProperties;

    /**
     * 短信验证码
     *
     * @param mobile 用户手机号
     */
    @GetMapping("/sms/{mobile}")
    public Result<Void> smsCode(@NotBlank(message = "{captcha.mobile.blank}") @PathVariable String mobile) {
        String code = RandomUtil.randomNumbers(4);
        RedisUtils.setCacheObject(GlobalConstants.CAPTCHA_CODE_KEY, mobile, code, Duration.ofMinutes(Constants.CAPTCHA_EXPIRATION));
        return Result.ok();
    }

    /**
     * 邮箱验证码
     *
     * @param email 邮箱
     */
    @GetMapping("/email/code")
    public Result<Void> emailCode(@NotBlank(message = "{user.email.not.blank}") String email) {
        if (!mailProperties.getEnabled()) {
            return Result.fail(ResultEnum.CONFLICT.getCode(), "当前系统没有开启邮箱功能！");
        }
        String code = RandomUtil.randomNumbers(4);
        RedisUtils.setCacheObject(GlobalConstants.CAPTCHA_CODE_KEY, email, code, Duration.ofMinutes(Constants.CAPTCHA_EXPIRATION));
        try {
            MailUtils.sendText(email, "登录验证码", "您本次验证码为：" + code + "，有效性为" + Constants.CAPTCHA_EXPIRATION + "分钟，请尽快填写。");
        } catch (Exception e) {
            log.error("验证码短信发送异常 => {}", e.getMessage());
            return Result.fail(ResultEnum.ERROR.getCode(), e.getMessage());
        }
        return Result.ok();
    }

    /**
     * 生成验证码
     */
    @GetMapping("/auth/code")
    public Result<CaptchaModel> getCode(@RequestParam(required = false, name = "clientId") String clientId,
                                        @RequestParam(required = false, name = "clientCode") String clientCode) {
        ClientBean model = null;
        if (StringUtils.isNotBlank(clientId)) {
            model = this.clientService.selectById(clientId);
        } else if (StringUtils.isNotBlank(clientCode)) {
            model = this.clientService.selectOne(new LambdaQueryWrapper<SysClient>().eq(SysClient::getCode, clientCode));
        }
        if (model == null) {
            return Result.fail(ResultEnum.DATA_VALIDATED_FAILED.getCode(), "客户端信息不能为空");
        }
        CaptchaModel captchaModel = new CaptchaModel();
        if (CaptchaTypeEnums.NONE.getCode().equalsIgnoreCase(model.getCaptcha())) {
            captchaModel.setEnable(false);
            return Result.ok(captchaModel);
        }
        captchaModel = this.baseService.generateCaptcha(CaptchaTypeEnums.getByCode(model.getCaptcha()));
        return Result.ok(captchaModel);
    }

}
